package org.arneca.hazelcached;

import java.net.InetSocketAddress;

import org.apache.commons.cli.CommandLine;
import org.apache.commons.cli.CommandLineParser;
import org.apache.commons.cli.HelpFormatter;
import org.apache.commons.cli.Options;
import org.apache.commons.cli.PosixParser;
import org.arneca.hazelcached.impl.HazelcastCacheImpl;

import com.thimbleware.jmemcached.MemCacheDaemon;

public class HazelCachedDaemon {

    static final String version = "0.0.1";
    static boolean      binary  = false;

    public static void main(String args[]) throws Exception {
        Options options = new Options();
        options.addOption("h", "help", false, "print this help screen");
        options.addOption("p", "port", true, "port to listen on");
        options.addOption("l", "listen", true, "Address to listen on");
        options.addOption("b", "binary", false, "binary protocol mode");
        options.addOption("V", false, "Show version number");
        options.addOption("v", false, "verbose (show commands)");

        // read command line options
        CommandLineParser parser = new PosixParser();
        CommandLine cmdline = parser.parse(options, args);

        if (cmdline.hasOption("help") || cmdline.hasOption("h")) {
            System.out.println("Hazelcached Version "+version);
            System.out.println("Memcached Version " + MemCacheDaemon.memcachedVersion);
            System.out.println("http://code.google.com/p/hazelcached");

            HelpFormatter formatter = new HelpFormatter();
            formatter.printHelp("HazelCachedDaemon", options);
            return;
        }
        
        if (cmdline.hasOption("b")) {
            binary = true;
        }

        int port = 11211;
        try {
            if (cmdline.hasOption("p")) {
                port = Integer.parseInt(cmdline.getOptionValue("p"));
            } else if (cmdline.hasOption("port")) {
                port = Integer.parseInt(cmdline.getOptionValue("port"));
            }
        } catch (NumberFormatException nfe) {
            System.out.println("Invalid port number");
            return;
        }

        InetSocketAddress addr = new InetSocketAddress(port);
        if (cmdline.hasOption("l")) {
            addr = new InetSocketAddress(cmdline.getOptionValue("l"), port);
        } else if (cmdline.hasOption("listen")) {
            addr = new InetSocketAddress(cmdline.getOptionValue("listen"), port);
        }

        final MemCacheDaemon daemon = new MemCacheDaemon();

        daemon.setBinary(binary);
        daemon.setAddr(addr);
        daemon.setCache(new HazelcastCacheImpl("default"));
        daemon.start();
        
        Runtime.getRuntime().addShutdownHook(new Thread(new Runnable() {
            public void run() {
                if (daemon != null && daemon.isRunning()) daemon.stop();
            }
        }));

    }
}
